﻿[assembly: System.Web.UI.WebResource("BM.Tools.WebControls.MForm.Controls.Validators.RootValidator.js", "application/x-javascript")]
[assembly: System.Web.UI.WebResource("BM.Tools.WebControls.MForm.Controls.Validators.RootValidator.debug.js", "application/x-javascript")]

namespace BM.Tools.WebControls.MForm.Controls.Validators
{
    using System;    
    using System.Collections.ObjectModel;
    using System.ComponentModel;    
    using System.Linq;
    using System.Web.UI;
    using System.Web.UI.WebControls;

    using AjaxControlToolkit;

    using BM.Tools.WebControls.MForm.Controls.Items;
    using BM.Tools.WebControls.MForm.ScriptReferences;

    /// <summary>
    /// The validator class for the Root control
    /// </summary>
    [DesignTimeVisible(false)]
    [ClientScriptResource("BM.Tools.WebControls.MForm",
            "BM.Tools.WebControls.MForm.Controls.Validators.RootValidator.js")]
    public class RootValidator : BaseValidator
    {
        private Collection<ErrorCause> errorCauses = new Collection<ErrorCause>();               

        /// <summary>
        /// Initializes a new instance of the <see cref="RootValidator"/> class.
        /// </summary>
        /// <param name="root">
        /// The root control.
        /// </param>
        public RootValidator(Root root)
        {
            Root = root;            
        }

        /// <summary>
        /// Gets ClientID.
        /// </summary>
        /// <value>
        /// The client id.
        /// </value>
        public override string ClientID
        {
            get
            {
                return String.Concat(Root.ClientID, "_Validator");
            }
        }

        /// <summary>
        /// Gets or sets Placement of the validator.
        /// </summary>
        /// <value>
        /// The placement.
        /// </value>
        public ValidatorPlacement Placement
        {
            get;
            set;
        }

        /// <summary>
        /// Gets the offspring items that reported the error.
        /// </summary>
        public Collection<ErrorCause> ErrorCauses
        {
            get
            {
                return errorCauses;
            }                 
        }

        /// <summary>
        /// Gets the Root control.
        /// </summary>
        public Root Root
        {
            get;
            private set;
        }

        /// <summary>
        /// Adds the HTML attributes and styles that need to be rendered for the control to the specified <see cref="T:System.Web.UI.HtmlTextWriter"></see> object.
        /// </summary>
        /// <param name="writer">
        /// An <see cref="T:System.Web.UI.HtmlTextWriter"></see> that represents the output stream to render HTML content on the client.
        /// </param>
        protected override void AddAttributesToRender(HtmlTextWriter writer)
        {
            ControlToValidate = string.Empty;
            base.AddAttributesToRender(writer);
            Page.ClientScript.RegisterExpandoAttribute(ClientID, "rootId", Root.ClientID + "_1");
            Page.ClientScript.RegisterExpandoAttribute(ClientID, "evaluationfunction", "BM.RootValidator.run", false);
        }

        /// <summary>
        /// Determines if the validator is bound to a root control
        /// </summary>        
        /// <returns>
        /// true if the root is not null
        /// </returns>                
        protected override bool ControlPropertiesValid()
        {
            return Root != null;
        }

        /// <summary>
        /// checks validity of the root
        /// </summary>
        /// <returns>
        /// is data inside root control valid
        /// </returns>
        protected override bool EvaluateIsValid()
        {
            foreach (OffspringItem item in Root.Items)
            {
                if (item.Validate(this) == false)
                {
                    ErrorMessage = string.Join(@"<br />", ErrorCauses.Select(errorCause => errorCause.ErrorText).ToArray());
                    return false;
                }
            }

            return true;
        }

        /// <summary>
        /// includes scripts
        /// </summary>
        /// <param name="e">
        /// The event args.
        /// </param>
        protected override void OnPreRender(EventArgs e)
        {
            base.OnPreRender(e);
            ScriptIncluder.IncludeResources(this);
        }

        /// <summary>
        /// renders the control
        /// </summary>
        /// <param name="writer">
        /// The writer.
        /// </param>
        protected override void Render(HtmlTextWriter writer)
        {
            if (DesignMode)
            {
                return;
            }

            base.Render(writer);
        }

        // ReSharper disable UnusedMember.Local

        /// <summary>
        /// serialization method
        /// </summary>
        private void ResetControlToValidate()
        {
            ControlToValidate = Root.ID;
        }

        /// <summary>
        /// serialization method
        /// </summary>
        /// <returns>
        /// should serialize ControlToValidate
        /// </returns>
        private bool ShouldSerializeControlToValidate()
        {
            return ControlToValidate != Root.ID;
        }

        // ReSharper restore UnusedMember.Local
    }
}